iT邦幫忙

2024 iThome 鐵人賽

DAY 10
0
Software Development

輕鬆學習設計模式Design Pattern系列 第 10

Day 10 建造者模式 Builder Pattern

  • 分享至 

  • xImage
  •  

當你進入餐廳點餐時,菜單上琳瑯滿目的選擇可能讓你感到無從下手。你可以選擇一個套餐,但如果你有特別的需求,例如多點一份沙拉,少放一點醬料,這時候就需要進行個性化的訂單。而這樣的流程,正是建造者模式 Builder Pattern 的精髓所在。它不僅在生活中隨處可見,在軟體設計中更是強大而實用的一種模式。

什麼是建造者模式?

建造者模式是一種建立型設計模式,它將物件的建立過程分解為多個步驟,並且可以根據需求有選擇地組合這些步驟,最終產生我們所需的物件。這樣的設計模式特別適合用於那些需要一步步構建,且每一步可能有不同選擇的複雜物件。

建造者模式通常包含以下角色:

  1. Product(產品):最終被構建的複雜物件。
  2. Builder(建造者):定義構建物件的抽象介面。
  3. ConcreteBuilder(具體建造者):實現 Builder 介面,提供具體的構建步驟。
  4. Director(指揮者):負責使用建造者來構建產品,控制建造的過程。

建造者模式在訂製汽車中的應用

讓我們以訂製汽車為例來說明建造者模式的應用。想像你正在購買一輛新車,經銷商會給你提供一系列選項,從引擎、輪胎到內裝,你可以自由選擇搭配,打造一輛專屬於你的車輛。這正是建造者模式最典型的應用場景。

我們需要定義最終要建造的產品 Car 類別,

// 產品類 Product
class Car {
private:
    std::string engine;
    std::string wheels;
    std::string interior;

public:
    void setEngine(const std::string& engineType) {
        engine = engineType;
    }

    void setWheels(const std::string& wheelType) {
        wheels = wheelType;
    }

    void setInterior(const std::string& interiorType) {
        interior = interiorType;
    }

    void showSpecifications() const {
        std::cout << "Engine: " << engine << "\n"
                  << "Wheels: " << wheels << "\n"
                  << "Interior: " << interior << std::endl;
    }
};

再定義一個 Builder 介面,它包含了構建汽車各部分的方法,

// 建造者介面 Builder
class CarBuilder {
public:
    virtual void buildEngine() = 0;
    virtual void buildWheels() = 0;
    virtual void buildInterior() = 0;
    virtual Car* getCar() = 0;
    virtual ~CarBuilder() = default;
};

接著我們建立具體的建造者類別,例如一個豪華汽車的建造者,

// 具體建造者 ConcreteBuilder
class LuxuryCarBuilder : public CarBuilder {
private:
    Car* car;

public:
    LuxuryCarBuilder() {
        car = new Car();
    }

    void buildEngine() override {
        car->setEngine("V8 Turbo Engine");
    }

    void buildWheels() override {
        car->setWheels("Alloy Wheels");
    }

    void buildInterior() override {
        car->setInterior("Leather Interior");
    }

    Car* getCar() override {
        return car;
    }
};

然後我們建立一個指揮者來控制建造的過程,

// 指揮者 Director
class CarDirector {
private:
    CarBuilder* builder;

public:
    CarDirector(CarBuilder* builder) : builder(builder) {}

    Car* construct() {
        builder->buildEngine();
        builder->buildWheels();
        builder->buildInterior();
        return builder->getCar();
    }
};

當你需要訂製一輛豪華汽車時,只需透過建造者模式來構建它,

int main() {
    CarBuilder* builder = new LuxuryCarBuilder();
    CarDirector director(builder);
    Car* car = director.construct();

    car->showSpecifications();

    delete car;
    delete builder;

    return 0;
}

這樣的設計讓我們可以輕鬆地改變汽車的設定,或者在需要時引入新的建造者,而不必修改現有的邏輯。建造者模式提供了靈活的物件構建過程,使得我們可以在不同需求下產生不同的產品。

建造者模式的優缺點

建造者模式的優點在於它的靈活性和可擴展性。由於構建過程是分步驟進行的,我們可以輕鬆地在不同的情境下進行客製化,無論是增加新功能還是修改現有步驟,都不會影響整個系統的設計。這樣的設計模式特別適合那些物件結構複雜且需要逐步構建的場景。

建造者模式也有缺點。由於每一個具體建造者都必須實現所有的建造步驟,這會導致大量的程式碼重複,特別是在類似的建造者之間。並且當物件的構建步驟過多時,可能會使得建造者變得臃腫,降低了程式碼的可讀性與維護性。另外指揮者雖然讓建造過程更具組織性,但也可能產生額外的複雜度。

總結

建造者模式特別適合於建立複雜物件或者需要靈活設定的物件。它就像是一個精密的工廠流水線,可以根據不同的需求生產出不同的產品,而且每個產品都保持品質與一致性。在現代軟體開發中,無論是複雜的汽車製造、蓋房屋,還是表單產生器,建造者模式都能幫助我們應對,當你下次面對需要建立複雜物件,或者需要根據不同情況建立不同類型物件的場景時,不妨考慮使用建造者模式。它可能正是你解決問題的關鍵。

更多C++語言相關的文章,歡迎追蹤我的部落格。
https://shengyu7697.github.io/cpp-builder-pattern/


上一篇
Day 9 命令模式 Command Pattern
下一篇
Day 11 轉接器模式 Adapter Pattern
系列文
輕鬆學習設計模式Design Pattern30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言